﻿using AutoMapper;
using MediatR;
using Microsoft.Data.SqlClient;
using Microsoft.EntityFrameworkCore;
using S.Common.Enums.Archives;
using S.Common.Enums.Initial;
using S.Common.helper;
using S.EliminationOrDath.API.Dtos;
using S.EliminationOrDath.Domain.Enums;
using S.EliminationOrDath.Domain.Models;
using S.EliminationOrDath.Infrastructure;
using S.EliminationOrDath.Infrastructure.Interface;
using S.EliminationOrDath.Read.API.Dtos;
using System.Text;
using static S.EliminationOrDath.API.Application.Command.EOrDCommand.EliminationReadCommand;

namespace S.EliminationOrDath.API.Application.CommandHandlers.EOrDCommandHandler
{
    /// <summary>
    /// 中介者方法实现类--淘汰
    /// </summary>
    public class EliminationReadCommandHandler : IRequestHandler<GetEliminationAllCommand, IQueryable?>, IRequestHandler<GetTypesCommand, List<TypesDtos>?>, IRequestHandler<GetVarietyEnumsCommand, List<TypesDtos>?>, IRequestHandler<GetPhaseOutReasonCommand, List<TypesDtos>?>, IRequestHandler<GetTreatmentMeasureCommand, List<TypesDtos>?>, IRequestHandler<EliminationmanagementCommand, PagingDto<EliminationDtos>>, IRequestHandler<EliminationmanagementIdCommand, EliminationModel>, IRequestHandler<GetArchivesCommand, List<SheepFileDto>>, IRequestHandler<EliminationmanagementEarTagCommand, EliminationModel>
    {
        private readonly IEliminationRepository er;
        private readonly IMapper mapper;
        private readonly DBHelper db;
        private readonly IConfiguration configuration;
        private readonly IHttpContextAccessor httpContextAccessor;

        public EliminationReadCommandHandler(IEliminationRepository er, IMapper mapper, DBHelper db, IConfiguration configuration, IHttpContextAccessor httpContextAccessor)
        {
            this.er = er;
            this.mapper = mapper;
            this.db = db;
            this.configuration = configuration;
            this.httpContextAccessor = httpContextAccessor;
        }

        #region 查询绑定

        /// <summary>
        /// 查询显示所有淘汰信息
        /// </summary>
        /// <param name="request"></param>
        /// <param name="cancellationToken"></param>
        /// <returns></returns>
        public async Task<IQueryable?> Handle(GetEliminationAllCommand request, CancellationToken cancellationToken)
        {
            return await er.GetAll();
        }
        /// <summary>
        /// 显示类型
        /// </summary>
        /// <param name="request"></param>
        /// <param name="cancellationToken"></param>
        /// <returns></returns>
        public async Task<List<TypesDtos>?> Handle(GetTypesCommand request, CancellationToken cancellationToken)
        {
            List<TypesDtos> typesDtos = new List<TypesDtos>();

            Type enumType = typeof(Types);
            if (enumType.IsEnum)
            {
                foreach (object value in Enum.GetValues(enumType))
                {
                    TypesDtos dto = new TypesDtos();

                    dto.Name = Enum.GetName(enumType, value);
                    dto.Value = (int)value;

                    typesDtos.Add(dto);
                }
            }

            return typesDtos;
        }
        /// <summary>
        /// 显示品种
        /// </summary>
        /// <param name="request"></param>
        /// <param name="cancellationToken"></param>
        /// <returns></returns>
        public async Task<List<TypesDtos>?> Handle(GetVarietyEnumsCommand request, CancellationToken cancellationToken)
        {
            List<TypesDtos> typesDtos = new List<TypesDtos>();

            Type enumType = typeof(VarietyEnum);
            if (enumType.IsEnum)
            {
                foreach (object value in Enum.GetValues(enumType))
                {
                    TypesDtos dto = new TypesDtos();

                    dto.Name = Enum.GetName(enumType, value);
                    dto.Value = (int)value;

                    typesDtos.Add(dto);
                }
            }

            return typesDtos;
        }
        /// <summary>
        /// 显示淘汰原因
        /// </summary>
        /// <param name="request"></param>
        /// <param name="cancellationToken"></param>
        /// <returns></returns>
        public async Task<List<TypesDtos>?> Handle(GetPhaseOutReasonCommand request, CancellationToken cancellationToken)
        {
            List<TypesDtos> typesDtos = new List<TypesDtos>();

            Type enumType = typeof(PhaseOutReason);
            if (enumType.IsEnum)
            {
                foreach (object value in Enum.GetValues(enumType))
                {
                    TypesDtos dto = new TypesDtos();

                    dto.Name = Enum.GetName(enumType, value);
                    dto.Value = (int)value;

                    typesDtos.Add(dto);
                }
            }

            return typesDtos;
        }
        /// <summary>
        /// 显示处理措施
        /// </summary>
        /// <param name="request"></param>
        /// <param name="cancellationToken"></param>
        /// <returns></returns>
        public async Task<List<TypesDtos>?> Handle(GetTreatmentMeasureCommand request, CancellationToken cancellationToken)
        {
            List<TypesDtos> typesDtos = new List<TypesDtos>();

            Type enumType = typeof(TreatmentMeasure);
            if (enumType.IsEnum)
            {
                foreach (object value in Enum.GetValues(enumType))
                {
                    TypesDtos dto = new TypesDtos();

                    dto.Name = Enum.GetName(enumType, value);
                    dto.Value = (int)value;

                    typesDtos.Add(dto);
                }
            }

            return typesDtos;
        }

        #endregion
        /// <summary>
        /// 淘汰管理列表显示
        /// </summary>
        /// <param name="request"></param>
        /// <param name="cancellationToken"></param>
        /// <returns></returns>
        public async Task<PagingDto<EliminationDtos>> Handle(EliminationmanagementCommand request, CancellationToken cancellationToken)
        {
            StringBuilder sqlBuilder = new StringBuilder(@"SELECT 
                                                        a.*, 
                                                        b.BirthDate, 
                                                        DATEDIFF(DAY, b.BirthDate, a.ReviewTime) AS DayAge, 
                                                        DATEDIFF(MONTH, b.BirthDate, a.ReviewTime) AS MonthAge
                                                    FROM 
                                                        EliminationModel a
                                                    JOIN 
                                                        SheepFileModel b 
                                                    ON 
                                                        a.EarTag = b.EarTag 
                                                    WHERE 
                                                        1=1");

            List<SqlParameter> parameters = new List<SqlParameter>();

            if (request.StartDate != null)
            {
                sqlBuilder.Append(" AND a.CreateDate >= @StartDate");
                parameters.Add(new SqlParameter("@StartDate", request.StartDate));
            }

            if (request.EndDate != null)
            {
                sqlBuilder.Append(" AND a.CreateDate <= @EndDate");
                parameters.Add(new SqlParameter("@EndDate", request.EndDate));
            }

            if (!string.IsNullOrEmpty(request.EarTag))
            {
                sqlBuilder.Append(" AND a.EarTag LIKE @EarTag");
                parameters.Add(new SqlParameter("@EarTag", "%" + request.EarTag + "%"));
            }

            if (request.OutReason != 0)
            {
                sqlBuilder.Append(" AND a.PhaseOutReason = @OutReason");
                parameters.Add(new SqlParameter("@OutReason", request.OutReason));
            }

            if (request.LeaveOrNot != null)
            {
                sqlBuilder.Append(" AND a.DepartureState = @LeaveOrNot");
                parameters.Add(new SqlParameter("@LeaveOrNot", request.LeaveOrNot));
            }

            // Get total count
            string countSql = "SELECT COUNT(*) FROM (" + sqlBuilder.ToString() + ") AS CountTable";
            int totalCount = db.ExecuteScalar(countSql, parameters.ToArray());

            // Clear the parameters list before reusing it
            parameters.Clear();

            // Re-add the parameters for the next query
            if (request.StartDate != null)
            {
                parameters.Add(new SqlParameter("@StartDate", request.StartDate));
            }

            if (request.EndDate != null)
            {
                parameters.Add(new SqlParameter("@EndDate", request.EndDate));
            }

            if (!string.IsNullOrEmpty(request.EarTag))
            {
                parameters.Add(new SqlParameter("@EarTag", "%" + request.EarTag + "%"));
            }

            if (request.OutReason != 0)
            {
                parameters.Add(new SqlParameter("@OutReason", request.OutReason));
            }

            if (request.LeaveOrNot != null)
            {
                parameters.Add(new SqlParameter("@LeaveOrNot", request.LeaveOrNot));
            }

            // Add pagination to the SQL
            sqlBuilder.Append(" ORDER BY a.CreateDate DESC, a.EliminationId OFFSET @Offset ROWS FETCH NEXT @Fetch ROWS ONLY");
            parameters.Add(new SqlParameter("@Offset", (request.pageIndex - 1) * request.pageSize));
            parameters.Add(new SqlParameter("@Fetch", request.pageSize));

            // Get the data
            List<EliminationDtos> data = await db.GetListDataBySqlWhere<EliminationDtos>(sqlBuilder.ToString(), parameters.ToArray());

            int pageCount = (int)Math.Ceiling((totalCount * 1.0) / request.pageSize);

            return new PagingDto<EliminationDtos>() { totalCount = totalCount, pageCount = pageCount, list = data };
        }
        /// <summary>
        /// 通过Id获取对应的淘汰数据
        /// </summary>
        /// <param name="request"></param>
        /// <param name="cancellationToken"></param>
        /// <returns></returns>
        public async Task<EliminationModel> Handle(EliminationmanagementIdCommand request, CancellationToken cancellationToken)
        {
            return await (await er.GetAll()).FirstOrDefaultAsync(m => m.EliminationId == request.Id);
        }
        /// <summary>
        /// 通过耳号查询档案信息
        /// </summary>
        /// <param name="request"></param>
        /// <param name="cancellationToken"></param>
        /// <returns></returns>
        public async Task<List<SheepFileDto>> Handle(GetArchivesCommand request, CancellationToken cancellationToken)
        {
            var list = GetSheepState(request.EarTag,configuration);
            return list;
        }
        /// <summary>
        /// 根据耳号查询对应信息
        /// </summary>
        /// <param name="request"></param>
        /// <param name="cancellationToken"></param>
        /// <returns></returns>
        public async Task<EliminationModel> Handle(EliminationmanagementEarTagCommand request, CancellationToken cancellationToken)
        {
            var list = await er.GetAll();
            return await list.FirstOrDefaultAsync(m=>m.EarTag == request.EarTag);
        }
        /// <summary>
        /// 显示耳号信息
        /// </summary>
        /// <returns></returns>
        private static List<SheepFileDto> GetSheepState(string ear,IConfiguration configuration)
        {
            var conf = configuration.GetValue<string>("WebApiIp");
            return HttpClientHelper.GetResponseList<SheepFileDto>(conf + "/ach/api/SheepFileModel/GetSheepFilesByEarTag?EarTag=" + ear);
        }
        /// <summary>
        /// 显示栋舍
        /// </summary>
        /// <returns></returns>
        private static List<ColumnListDto> GetColumn(IConfiguration configuration)
        {
            var conf = configuration.GetValue<string>("WebApiIp");
            return HttpClientHelper.GetResponseList<ColumnListDto>(conf + "/Authorization/api/ColumnManagement/GetColumnList");
        }
        /// <summary>
        /// 显示栏位
        /// </summary>
        /// <returns></returns>
        private static List<ColumnListDto> GetFieldMode(IConfiguration configuration)
        {
            var conf = configuration.GetValue<string>("WebApiIp");
            return HttpClientHelper.GetResponseList<ColumnListDto>(conf + "/Authorization/api/ColumnManagement/GetFieldMode");
        }
    }
}
